package org.tri.entity;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.OneToMany;
import javax.persistence.Table;
import org.hibernate.annotations.Cascade;

/**
 * La clase {@code Venta} almacena los datos permitentes a una venta, incluyendo los animales asociados a la misma
 * @author Lucas Giacomazzi
 * @version 1.0, Nov 16, 2011
 */
@Entity
@Table ( name = "venta" )
public class Venta extends AbstractVenta {

    /** Lista de animales correspondientes a la venta. */
    private List<Animal> animales = new ArrayList<Animal>();
    
    /**
     * Constructor sin parámetros para uso de hibernate.
     */
    public Venta() {
        super();
        
    }//end constructor
    
    /**
     * Constructor que permite asignar el establecimiento y la 
     * fecha de la venta.
     * @param establecimiento establecimiento al que corresponde la venta.
     * @param fecha fecha en la que se realizó la venta.
     */
    public Venta( Establecimiento establecimiento, Date fecha ) {
        super();
        setEstablecimiento( establecimiento );
        setFecha( fecha );
        
    }//end constructor

    /**
     * Nos permite obtener una lista con los animales asociadas a la venta.
     * @return List<Animal> lista de animales
     */
    @OneToMany ( cascade = { CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH },
                 mappedBy = "venta" )
    @Cascade ( { org.hibernate.annotations.CascadeType.SAVE_UPDATE,
                 org.hibernate.annotations.CascadeType.EVICT } )
    public List<Animal> getAnimales() {
        return animales;

    }//end método getAnimales

    /**
     * Nos permite cambiar una lista de animales asociados a la venta 
     * por otra lista de animales.
     * Este método es utilizado exclusivamente por Hibernate para asignar
     * los datos de los animales obtenidos de la base de datos.
     * @param animales List<Aniamal> lista de animales
     */
    protected void setAnimales( List<Animal> animales ) {
        this.animales = animales;

    }//end método setAnimales   

    /**
     * {@inheritDoc}
     */
    @Override
    public void agregarAnimal( Animal animal ) {
        animal.setVenta( this );

        getAnimales().add( animal );
        
        this.setCantidadAnimales( getAnimales().size() );

    }//end método agregarAnimal

    /**
     * {@inheritDoc}
     */
    @Override
    public void agregarAnimales( List<Animal> animales ) {
        for ( Animal animal : animales )
            agregarAnimal( animal );

    }//end método agregarAnimales

    /**
     * {@inheritDoc}
     */
    @Override
    public List<AbstractAnimal> obtenerAnimales() {
        List<AbstractAnimal> anim = new ArrayList<AbstractAnimal>();

        anim.addAll( getAnimales() );
        
        return anim;

    }//end método obtenerAnimales

    @Override
    public void eliminarAnimal(Animal animal) {
        animal.setVenta(null);
        this.animales.remove(animal);
        
        this.setCantidadAnimales( getAnimales().size() );
        
    }

    @Override
    public void eliminarAnimales(List<Animal> animales) {
        for(Animal a: animales){
            eliminarAnimal(a);
            
        }
                
    }

}//end clase Venta

